package com.ibm.psbc.cloud.common.contextcarrier.feign;

import java.io.IOException;
import java.util.HashMap;
import java.util.Map;

import com.ibm.iisp.common.util.BeanFactory;
import com.ibm.psbc.cloud.common.contextcarrier.ContextUtils;

import lombok.extern.slf4j.Slf4j;
import okhttp3.Headers;
import okhttp3.Interceptor;
import okhttp3.Request;
import okhttp3.Request.Builder;
import okhttp3.Response;

/** Feign 客户端在调用服务前把Context数据转换成Request Header属性，传送到服务器，调用服务返回后，把Response Header
 * 中的相关属性转换成Context数据，放到ThreadLocal中。
 * 
 * @author johnny
 *
 * @param <T> Context的类型
 */
@Slf4j
public class ContextCarryInterceptor<T> implements Interceptor {
	
	private ContextUtils<T> contextUtils;
	@SuppressWarnings("unchecked")
	public ContextUtils<T> getContextUtils() {
    	if (contextUtils == null) {
    		contextUtils = BeanFactory.getInstance().getBean(ContextUtils.class);
    	}
		return contextUtils;
	}
	@Override
    public Response intercept(Chain chain) throws IOException {
    	log.trace("Start to call rest");
        Request request = chain.request();
        Map<String, String> contextData = getContextUtils().context2Map();
        Builder builder = request.newBuilder();
		for (Map.Entry<String, String> ent : contextData.entrySet()) {
			builder.addHeader(ent.getKey(), ent.getValue());
		}
        request = builder.build();

        Response response = chain.proceed(request);
        //log.trace("Hey there, this is my response: " + response.header("dummy-header"));
        Headers respHeaders = response.headers();
		HashMap<String, String> data = new HashMap<String, String>();
		for (String name : respHeaders.names()) {
			if (name.startsWith(ContextUtils.CONTEXT_HEAD_PREFIX)) {
				data.put(name, respHeaders.get(name));
			}
		}
		getContextUtils().map2Conext(data);
        log.trace("End to call rest");
        return response;
    }
}